﻿using AutoRegistDependency.Interface;
using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input;
using HandyControl.Controls;
using HandyWpf.Bus;
using Services.Base;
using HandyWpf.ViewModels.Base.Enum;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Markup;
using System.Windows;
using System.Collections;
using Models.Entities.SystemEntities;
using System.Windows.Controls;

namespace HandyWpf.ViewModels.Base
{
    /// <summary>
    /// 基类 包含基本的增删改查
    /// </summary>
    /// <typeparam name="T">实体的类型</typeparam>
    /// <typeparam name="TQuery">查询实体</typeparam>
    /// <typeparam name="TPrimaryKey">实体主键类型</typeparam>
    /// /// <typeparam name="TFormPage">新增、编辑页面类型</typeparam>
    public abstract partial class BasePageCRUDViewModel<T,TQuery,IBaseService,TPrimaryKey,TFormPage>:BasePagedViewModel<T,TQuery, IBaseService<T>>
        where T:class,new()
        where TQuery : ObservableObject,new()
    {
        /// <summary>
        /// 事件总线，用来处理对话框开启和关闭事件
        /// </summary>
        protected IEventBus eventBus;
        /// <summary>
        /// handycontrol组件 父组件的消息标记 hc:Dialog.Token的值
        /// </summary>
        public abstract string DialogToken { get;}
        /// <summary>
        /// datagrid选中的列
        /// </summary>
        public List<T> SelectedValues { get; set; } = new();
        /// <summary>
        /// 表单mvvm对象
        /// </summary>
        [ObservableProperty]
        private T form=new();
        /// <summary>
        /// 当前表单的状态
        /// </summary>
        [ObservableProperty]
        private FormStatus formStatus;
        /// <summary>
        /// 当前页面loading状态
        /// </summary>
        [ObservableProperty]
        private bool loading = false;
        /// <summary>
        /// ctor
        /// </summary>
        /// <param name="eventBus"></param>
        /// <param name="baseService"></param>
        public BasePageCRUDViewModel(IEventBus eventBus,IBaseService<T> baseService) : base(baseService)
        {
            this.eventBus = eventBus;
        }

        /// <summary>
        /// 处理表单新增操作
        /// </summary>
        [RelayCommand]
        public virtual void HandleAdd()
        {
            Loading = true;
            ClearForm();
            OpenCurrentPageDialog(typeof(TFormPage));
            FormStatus = FormStatus.Add;
        }
        /// <summary>
        /// 点击操作按钮时获取的数据详情
        /// </summary>
        /// <param name="primaryKey"></param>
        /// <returns></returns>
        public abstract T GetEntityById(TPrimaryKey primaryKey);
        /// <summary>
        /// 处理表单删除操作
        /// </summary>
        /// <param name="primaryKey"></param>
        [RelayCommand]
        public virtual void HandleDelete(TPrimaryKey primaryKey)
        {
            Loading = true;
            MessageBoxResult message= HandyControl.Controls.MessageBox.Ask("您确定删除此条数据？删除后不可恢复！", "删除提示");
            if (message == MessageBoxResult.OK)
            {
                var entity = GetEntityById(primaryKey);
                var r = baseService.Delete(entity);
                if (r)
                {
                    Growl.Success("删除成功！");
                    GetList();
                }
                else
                {
                    Growl.Error(message: "删除失败！");
                }
            }
            else
            {
                Growl.Info(message: "操作取消！");
            }
            Loading = false;
        }
        /// <summary>
        /// 处理表单修改操作
        /// </summary>
        /// <param name="primaryKey"></param>
        [RelayCommand]
        public virtual void HandleEdit(TPrimaryKey primaryKey)
        {
            Loading = true;
            ClearForm();
            var entity = GetEntityById(primaryKey);
            Form = entity;
            OpenCurrentPageDialog(typeof(TFormPage));
            FormStatus = FormStatus.Edit;

        }
        /// <summary>
        /// 查看详情操作
        /// </summary>
        /// <param name="primaryKey"></param>
        [RelayCommand]
        public virtual void HandleDetail(TPrimaryKey primaryKey)
        {
            HandleEdit(primaryKey);
            FormStatus = FormStatus.Detail;
        }
        /// <summary>
        /// datagrid选中事件
        /// </summary>
        /// <param name="items"></param>
        [RelayCommand]
        public virtual void SelectItems(IList selectValues)
        {
            if(selectValues != null)
            {
                SelectedValues = selectValues.Cast<T>().ToList();
            }
        }
        [RelayCommand]
        public virtual void HandleBatchDelete()
        {
            Loading = true;
            if (SelectedValues.Count() > 0)
            {
                MessageBoxResult message = HandyControl.Controls.MessageBox.Ask($"您确定删除{SelectedValues.Count()}条数据？删除后不可恢复！", "删除提示");
                if (message == MessageBoxResult.OK)
                {
                    bool r= baseService.Delete(SelectedValues);
                    if (r)
                    {
                        Growl.Success("删除成功！");
                        GetList();
                    }
                    else
                    {
                        Growl.Error("删除失败！");
                    }
                }
            }
            Loading = false;
        }
        /// <summary>
        /// 表单页面的新增操作命令
        /// </summary>
        [RelayCommand]
        public virtual void FormAdd()
        {
            var r = baseService.Add(Form);
            if (r)
            {
                Growl.Success("新增成功！");
                GetList();
            }
            else
            {
                Growl.Error("新增失败！");
            }
            Loading=false;
            CloseCurrentPageDialog(typeof(TFormPage));
        }
        /// <summary>
        /// 表单页面的新增修改命令
        /// </summary>
        [RelayCommand]
        public virtual void FormEdit()
        {
            var r = baseService.Update(Form);
            if (r)
            {
                Growl.Success("修改成功！");
                GetList();
            }
            else
            {
                Growl.Error("修改失败！");
            }
            Loading=false;
            CloseCurrentPageDialog(typeof(TFormPage));
        }

        /// <summary>
        /// 清空Query对象
        /// </summary>
        [RelayCommand]
        public virtual void ClearQuery()
        {
            this.Query = new();
        }
        /// <summary>
        /// 关闭当前页面的对话框
        /// </summary>
        [RelayCommand]
        public virtual void Cancel()
        {
            Loading = false;
            CloseCurrentPageDialog(typeof(TFormPage));
            Growl.Info("取消操作");
        }
        /// <summary>
        /// 清空Form对象
        /// </summary>
        protected virtual void ClearForm()
        {
            Form=new();
        }

        /// <summary>
        /// 打开当前页面的dialog
        /// </summary>
        /// <param name="dialogPage">控件类型(必须已经依赖注入)</param>
        protected void OpenCurrentPageDialog(Type dialogPage)
        {
            var eventData = new DialogEventData()
            {
                TragetType = dialogPage,
                Token = DialogToken
            };
            eventBus.Publish(eventData);
        }
        /// <summary>
        /// 关闭当前页面的Dialog
        /// </summary>
        /// <param name="dialogPage">控件类型(必须已经依赖注入)</param>
        protected void CloseCurrentPageDialog(Type dialogPage)
        {
            var eventData = new DialogEventData()
            {
                Open = false,
                TragetType = dialogPage,
                Token = DialogToken
            };
            eventBus.Publish(eventData);
        }
        /// <summary>
        /// 打开主窗口的Dialog
        /// </summary>
        /// <param name="dialogPage">控件类型(必须已经依赖注入)</param>
        protected void OpenMainWindowDialog(Type dialogPage)
        {
            var eventData = new DialogEventData()
            {
                TragetType = dialogPage,
            };
            eventBus.Publish(eventData);
        }
        /// <summary>
        /// 关闭主窗口Dialog
        /// </summary>
        /// <param name="dialogPage">控件类型(必须已经依赖注入)</param>
        protected void CloseMainWindowDialog(Type dialogPage)
        {
            var eventData = new DialogEventData()
            {
                Open = false,
                TragetType = dialogPage,
            };
            eventBus.Publish(eventData);
        }
    }
}
